#pragma once

#include "media.h"
#include "rtsp.h"
#include <QTcpSocket>
#include "AudioBuffer.h"
#include <fstream>
#include <QHostAddress>

namespace jlh
{
	class RtspRequest;
	class RtspResponse;
	class RTPConnection;
	class RtspConnection : public std::enable_shared_from_this<RtspConnection>
	{
	public:

		enum ConnectionMode
		{
			RTSP_SERVER,
			RTSP_PUSHER
		};

		enum ConnectionState
		{
			START_CONNECT,
			START_PLAY,
			START_PUSH
		};

		RtspConnection() = delete;
		RtspConnection(std::shared_ptr<Rtsp> rtsp_server, QTcpSocket* tcpSocket);
		virtual ~RtspConnection();

		MediaSessionId GetMediaSessionId()
		{
			return session_id_;
		}

		bool IsPlay() const
		{
			return conn_state_ == START_PLAY;
		}

		bool IsRecord() const
		{
			return conn_state_ == START_PUSH;
		}

		bool IsClosed();

		uint32_t GetSocket() {
			if (rtp_channel_)
			{
				return rtp_channel_->socketDescriptor();
			}
			return 0;
		}

		int GetId() { return 1; }

		void SendOptions(ConnectionMode mode = RTSP_SERVER);

		void DisConnect();

		void Send(const char* data, int data_size);

		QHostAddress GetPeerAddr();

	protected:
		void OnClose();
		void OnRead();
		void OnDisconnected();

		bool HandleRtspResponse(AudioBuffer& buffer);
		void SendAnnounce();
		void SendSetup();
		void HandleRecord();

		bool HandleRtspRequest(AudioBuffer& buffer);
		void HandleCmdOption();
		void HandleCmdDescribe();
		void HandleCmdSetup();
		void HandleCmdPlay();
		void HandleCmdTeardown();
		void HandleCmdGetParameter();

		void HandleRtcp(AudioBuffer&  buffer);

	private:
		void SendRtspMessage(std::shared_ptr<char>& buf, uint32_t size);

	private:
		std::weak_ptr<Rtsp> rtsp_;

		std::shared_ptr<QTcpSocket> rtp_channel_;

		ConnectionMode conn_mode_ = RTSP_SERVER;
		ConnectionState conn_state_ = START_CONNECT;
		MediaSessionId session_id_ = 0;

		std::unique_ptr<RtspRequest> rtsp_request_;
		std::unique_ptr<RtspResponse> rtsp_response_;
		AudioBuffer buffer_reader_;
		std::shared_ptr<RTPConnection> rtp_conn_;

		std::ofstream ofs_log_;
	};
}



